8.5 型タームを使った演算子の指定
type elementとtype termでジェネリクスの型制約を実現できる
type elementで定義されている型を変数やフィールド、戻り値、引数の型に指定するとコンパイル時のエラーとなるので注意
code:go
var zzz Integer = 123 // cannot use type Integer outside a type constraint: interface contains type constraints
type termはデフォルトでは完全に一致しなければいけない
code:go
type Integer interface {
int | int8 | int16 | int32 | int64 |
uint | uint8 | uint16 | uint32 | uint64 | uintptr
}
func divAndRemainderT Integer(num, denom T) (T, T, error) {
if denom == 0 {
return 0, 0, errors.New("0で割ることはできません")
}
return num / denom, num % denom, nil
}
func main() {
type MyInt int // intはIntegerに含まれてはいるがMyIntは含まれていない
var myA MyInt = 10
var myB MyInt = 20
fmt.Println(divAndRemainder(myA, myB)) //コンパイル時エラー MyInt does not satisfy Integer (possibly missing ~ for int in Integer)
}
~をつけることで基底型を許容することができる
code:go
type Integer interface {
~int | int8 | int16 | int32 | int64 |
uint | uint8 | uint16 | uint32 | uint64 | uintptr
}
// 省略
func main() {
type MyInt int
var myA MyInt = 10
var myB MyInt = 20
fmt.Println(divAndRemainder(myA, myB)) // MyIntの基底型はintなので許容 0 10 <nil>
}
type termは事前宣言された型以外にスライスやマップ、配列、チャネル、構造体、関数も指定できる
/icons/hr.icon
8.5.1 型推論とジェネリクス
8.5.2 型要素による定数の制約
8.5.3 ジェネリック関数とジェネリックなデータ構造の利用